package com.srit.core.sql;

import java.lang.reflect.Field;
import java.lang.reflect.ParameterizedType;

import org.springframework.jdbc.core.JdbcTemplate;

/**
 * 
 * @author guan
 * 
 */
public class BaseCRUD<T> {
	private JdbcTemplate jdbcTemplate;

	private Class<T> entityClass;

	private String tableName;
	private String saveSql;
	private Object[] saveArgs;
	private String updateSql;
	private Object[] updateArgs;
	private String maxIdSql;
	private String getByIdSql;
	private Object[] getByIdArgs;
	private String deleteSql;
	private String querySql;
	private String pageSqlCount;
	private String pageSql;

	public BaseCRUD() {
		entityClass = (Class<T>) ((ParameterizedType) getClass()
				.getGenericSuperclass()).getActualTypeArguments()[0];
	}

	public void initBaseSql() throws IllegalArgumentException,
			SecurityException, IllegalAccessException, NoSuchFieldException {
		this.tableName = entityClass.getDeclaredField("TABLENAME")
				.get(entityClass).toString();
		initSaveSql();
		initUpdateSql();
	}

	private void initSaveSql() throws SecurityException, NoSuchFieldException,
			IllegalArgumentException, IllegalAccessException {
		Field[] fields = entityClass.getDeclaredFields();
		StringBuffer sql = new StringBuffer("INSERT INTO " + this.tableName
				+ " ");
		StringBuffer sqlCompose = new StringBuffer("(");
		StringBuffer sqlValueCompose = new StringBuffer("VALUES (");
		for (int i = 0; i < fields.length; i++) {
			Field field = fields[i];
			if (!field.getName().equalsIgnoreCase("TABLENAME")) {
				String typeName = field.getType().getName();
				if ("java.lang.String".equals(typeName)
						|| "java.lang.Integer".equals(typeName)
						|| "int".equals(typeName)
						|| "java.util.Date".equals(typeName)) {
					sqlCompose.append(field.getName());
					if (field.getName().equalsIgnoreCase("ID")) {
						// TODO: squences
					}
					sqlValueCompose.append("?");
					sqlCompose.append(",");
					sqlValueCompose.append(",");
				} else {
					System.out.println(typeName);
				}
			}
		}
		sql.append(sqlCompose.substring(0, sqlCompose.length() - 1))
				.append(")");
		sql.append(sqlValueCompose.substring(0, sqlValueCompose.length() - 1))
				.append(")");
		System.out.println(sql.toString());
	}

	private void initUpdateSql() {
		Field[] fields = entityClass.getDeclaredFields();
		StringBuffer sql = new StringBuffer("UPDATE " + this.tableName
				+ " SET ");
		StringBuffer sqlCompose = new StringBuffer();
		for (int i = 0; i < fields.length; i++) {
			Field field = fields[i];
			if (!(field.getName().equalsIgnoreCase("TABLENAME") || field
					.getName().equalsIgnoreCase("ID"))) {
				String typeName = field.getType().getName();
				if ("java.lang.String".equals(typeName)
						|| "java.lang.Integer".equals(typeName)
						|| "int".equals(typeName)
						|| "java.util.Date".equals(typeName)) {
					sqlCompose.append(field.getName() + "=?");
					sqlCompose.append(",");
				} else {
					System.out.println(typeName);
				}
			}
		}
		sql.append(sqlCompose.substring(0, sqlCompose.length() - 1));
		System.out.println(sql);
	}

	private void initMaxIdSql() {
		System.out.println(" select max(ID) FROM " + this.tableName);
	}

	private void initGetByIdSql() {
		System.out.println("select * from " + this.tableName + " where id=?");
	}

	private void initQuerySql() {
		System.out.println("select * from " + this.tableName);
	}

	private void initPageSql() {
		String sqlCount = "select count(*) from " + tableName + " where 1=1 ";
		String sqlAnd = " ";
		String sqlSelect = "select t2.* " + "from (select rownum r,t1.* from "
				+ tableName + " t1 where rownum<? " + sqlAnd
				+ ") t2 where t2.r>?";

	}

	public void save() {
		System.out.println("Save");
		// jdbcTemplate.update(saveSql, saveArgs);
	}

	public static void main(String[] args) throws IllegalArgumentException,
			SecurityException, IllegalAccessException, NoSuchFieldException {
		TestBaseCRUD tttt = new TestBaseCRUD();
		tttt.initBaseSql();
	}
}

class TestBaseCRUD extends BaseCRUD<Test> {

}

class Test {
	public static final String TABLENAME = "t_test";

	private String name;
	private int id;

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public int getId() {
		return id;
	}

	public void setId(int id) {
		this.id = id;
	}

}
